#!/usr/bin/env python
# -*- coding: UTF-8 -*-
"""
@Project ：Employment_class 
@File    ：07_菜鸟教程_threading.py
@IDE     ：PyCharm 
@Author  ：XiaoDengYa
@Date    ：2021/6/9/009 17:02 
"""
import os

"""
threading模块方法：
    threading.currentThread()  返回当前的线程变量
    threading.enumerate() 返回正在运行的线程的list。正在运行指的是线程启动后，结束前。不包括启动前与终止的
    threading.activeCount() 返回正在运行的线程数量，与len(threading.enumerate())方法相同
    
    run() 表示线程活动的方法
    start() 启动线程活动
    join([timeout]) 等待至线程中止
    isAive() 返回线程是否活动的
    getName() 返回线程名
    setName() 设置线程名
"""

# import threading
# import time
#
# exitFlag = 0
#
#
# class myThread(threading.Thread):
#     def __init__(self, threadID, name, counter):
#         threading.Thread.__init__(self)
#         self.threadID = threadID
#         self.name = name
#         self.counter = counter
#
#     def run(self):
#         print("开始线程：" + self.name)
#         print_time(self.name, self.counter, 5)
#         print("退出线程：" + self.name)
#
#
# def print_time(threadName, delay, counter):
#     while counter:
#         if exitFlag:
#             threadName.exit()
#         time.sleep(delay)
#         print("%s: %s" % (threadName, time.ctime(time.time())))
#         counter -= 1
#
#
# # 创建新线程
# thread1 = myThread(1, "Thread-1", 1)
# thread2 = myThread(2, "Thread-2", 2)
#
# # 开启新线程
# thread1.start()
# thread2.start()
# thread1.join()
# thread2.join()
# print("退出主线程")


"""
线程同步
如果多个线程共同对某个数据修改，则可能出现不可预料的结果，为了保证数据的正确性，需要对多个线程进行同步。
使用 Thread 对象的 Lock 和 Rlock 可以实现简单的线程同步，这两个对象都有 acquire 方法和 release 方法，对于那些需要每次只允许一个线程操作的数据，可以将其操作放到 acquire 和 release 方法之间。如下：
多线程的优势在于可以同时运行多个任务（至少感觉起来是这样）。但是当线程需要共享数据时，可能存在数据不同步的问题。
考虑这样一种情况：一个列表里所有元素都是0，线程"set"从后向前把所有元素改成1，而线程"print"负责从前往后读取列表并打印。
那么，可能线程"set"开始改的时候，线程"print"便来打印列表了，输出就成了一半0一半1，这就是数据的不同步。为了避免这种情况，引入了锁的概念。
锁有两种状态——锁定和未锁定。每当一个线程比如"set"要访问共享数据时，必须先获得锁定；如果已经有别的线程比如"print"获得锁定了，那么就让线程"set"暂停，也就是同步阻塞；等到线程"print"访问完毕，释放锁以后，再让线程"set"继续。
经过这样的处理，打印列表时要么全部输出0，要么全部输出1，不会再出现一半0一半1的尴尬场面。
"""

# import threading
# import time
#
#
# class myThread(threading.Thread):
#     def __init__(self, threadID, name, counter):
#         threading.Thread.__init__(self)
#         self.threadID = threadID
#         self.name = name
#         self.counter = counter
#
#     def run(self):
#         print("开启线程： " + self.name)
#         # 获取锁，用于线程同步
#         threadLock.acquire()
#         print_time(self.name, self.counter, 3)
#         # 释放锁，开启下一个线程
#         threadLock.release()
#
#
# def print_time(threadName, delay, counter):
#     while counter:
#         time.sleep(delay)
#         print("%s: %s" % (threadName, time.ctime(time.time())))
#         counter -= 1
#
#
# threadLock = threading.Lock()
# threads = []
#
# # 创建新线程
# thread1 = myThread(1, "Thread-1", 1)
# thread2 = myThread(2, "Thread-2", 2)
#
# # 开启新线程
# thread1.start()
# thread2.start()
#
# # 添加线程到线程列表
# threads.append(thread1)
# threads.append(thread2)
#
# # 等待所有线程完成
# for t in threads:
#     t.join()
# print("退出主线程")

"""
线程优先级队列（ Queue）
Python 的 Queue 模块中提供了同步的、线程安全的队列类，包括FIFO（先入先出)队列Queue，LIFO（后入先出）队列LifoQueue，和优先级队列 PriorityQueue。
这些队列都实现了锁原语，能够在多线程中直接使用，可以使用队列来实现线程间的同步。
Queue 模块中的常用方法:
    Queue.qsize() 返回队列大小
    Queue.empty() 如果队列为空，返回True否则返回False
    Queue.full() 如果队列满了返回True否则返回False
    Queue.get([block[,timeout]]) 获取队列，timeout等待时间
    Queue.get_nowait()相当Queue.get(False)
    Queue.put(item) 写入队列，timeout等待时间
    Queue.put_nowait(item) 相当Queue.put(item, False)
    Queue.task_done() 在完成一项工作之后，Queue.task_done()函数向任务已经完成的队列发送一个信号
    Queue.join() 实际上意味着等到队列为空，再执行别的操作
"""

# import queue
# import threading
# import time
#
# exitFlag = 0
#
#
# class myThread(threading.Thread):
#     def __init__(self, threadID, name, q):
#         threading.Thread.__init__(self)
#         self.threadID = threadID
#         self.name = name
#         self.q = q
#
#     def run(self):
#         print("开启线程：" + self.name)
#         process_data(self.name, self.q)
#         print("退出线程：" + self.name)
#
#
# def process_data(threadName, q):
#     while not exitFlag:
#         queueLock.acquire()
#         if not workQueue.empty(): # 如果队列不为空则执行
#             data = q.get()
#             print(data)
#             queueLock.release()
#             print("%s processing %s" % (threadName, data))
#         else:
#             queueLock.release()
#         time.sleep(1)
#
#
# threadList = ["Thread-1", "Thread-2", "Thread-3"]
# nameList = ["One", "Two", "Three", "Four", "Five"]
# queueLock = threading.Lock()
# workQueue = queue.Queue(10)
# threads = []
# threadID = 1
#
# # 创建新线程
# for tName in threadList:
#     thread = myThread(threadID, tName, workQueue)
#     thread.start()
#     threads.append(thread)
#     threadID += 1
#
# # 填充队列
# queueLock.acquire()
# for word in nameList:
#     workQueue.put(word)
# queueLock.release()
#
# # 等待队列清空
# while not workQueue.empty():
#     pass
#
# # 通知线程是时候退出
# exitFlag = 1
#
# # 等待所有线程完成
# for t in threads:
#     t.join()
# print("退出主线程")


# 多进程copy文件

# from multiprocessing import Process
#
#
# class CopyProcess(Process):
#     def __init__(self,filepath):
#         Process.__init__(self)
#         self.filepath = filepath
#
#     def run(self):
#         file_list = os.listdir(self.filepath)
#         for file in file_list:
#             with open(self.filepath + "/" + file, "r", encoding="utf-8") as fr:
#                 frs = fr.read()
#             with open(self.mkdir_file()+"/"+file,"a+",encoding="utf-8") as fw:
#                 fw.write(frs)
#
#     def mkdir_file(self):
#         new_path = self.filepath + "复件"
#         if not os.path.exists(new_path):
#             os.mkdir(new_path)
#         return new_path
#
#
# if __name__ == '__main__':
#     path = r"F:\BaiduNetdiskDownload\python就业班\02Python核心编程\第3节 网络编程\第3节 网络编程\01.网络编程概述、SOCKET\源码\多进程copy文件\test"
#     C = CopyProcess(path)
#     C.start()


# from multiprocessing import Pool
#
# def run(filepath):
#         file_list = os.listdir(filepath)
#         for file in file_list:
#             with open(filepath + "/" + file, "r", encoding="utf-8") as fr:
#                 frs = fr.read()
#             with open(mkdir_file(filepath)+"/"+file,"a+",encoding="utf-8") as fw:
#                 fw.write(frs)
#
# def mkdir_file(filepath):
#     new_path = filepath + "复件"
#     if not os.path.exists(new_path):
#         os.mkdir(new_path)
#     return new_path
#
# if __name__ == '__main__':
#     file = r"F:\BaiduNetdiskDownload\python就业班\02Python核心编程\第3节 网络编程\第3节 网络编程\01.网络编程概述、SOCKET\源码\多进程copy文件\test"
#     pool = Pool(5)
#     pool.apply_async(run,args=(file,))
#     pool.close()
#     pool.join()

# from threading import Thread
#
# def run(filepath):
#         file_list = os.listdir(filepath)
#         for file in file_list:
#             with open(filepath + "/" + file, "r", encoding="utf-8") as fr:
#                 frs = fr.read()
#             with open(mkdir_file(filepath)+"/"+file,"a+",encoding="utf-8") as fw:
#                 fw.write(frs)
#
# def mkdir_file(filepath):
#     new_path = filepath + "复件"
#     if not os.path.exists(new_path):
#         os.mkdir(new_path)
#     return new_path
#
# if __name__ == '__main__':
#     file = r"F:\BaiduNetdiskDownload\python就业班\02Python核心编程\第3节 网络编程\第3节 网络编程\01.网络编程概述、SOCKET\源码\多进程copy文件\test"
#     t = Thread(target=run,args=(file,))
#     t.setDaemon(True)
#     t.start()
#     t.join()
